package com.sunyur.tailor.channel.common.middle.handler;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.sunyur.tailor.channel.common.middle.enums.MiddleResultEnum;
import com.sunyur.tailor.channel.common.middle.util.AESUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.PrintWriter;
import java.util.*;

/**
 *
 * @Author 99288
 * @Description 外部控制层拦截器，接口鉴权
 * @Date 15:00 2021/7/20
 * @Param
 * @return
 **/
@Slf4j
public class OuterControllerHandler implements HandlerInterceptor {

    @Value("${sunyur.key}")
    private String appKey;
    @Value("${sunyur.secret}")
    private String appSecret;

    /**
     * 有效时间30分钟
     */
    private static Long TIME =  30L * 60L * 1000L;

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
//        if(1==1)
//        {
//            return true;
//        }
        if("/outer/FS/Approval".equals( request.getServletPath()))
        {
            log.info("放行接口 {}",request.getServletPath());
            return Boolean.TRUE;
        }

        log.info("OuterControllerHandler preHandle path is {}", request.getServletPath());
        //获取令牌
        String token = request.getHeader("accessToken");
        if (StringUtils.isEmpty(token)) {
            setResponse(response, MiddleResultEnum.PAYMENT_REQUIRED.getCode(), MiddleResultEnum.PAYMENT_REQUIRED.getValue());
            return Boolean.FALSE;
        }
        log.info("OuterControllerHandler preHandle token is {}", token);
        //解密令牌
        String decrypt = AESUtil.decrypt(token, appKey);
        String[] split = decrypt.split("\\|");
        String key = split[0];
        String path = split[1];
        String timestamp = split[2];
        String secret = split[3];
        log.info("OuterControllerHandler preHandle appKey:{} path:{} timestamp:{} appSecret:{}", key, path, timestamp, secret);
        if(StringUtils.isAnyBlank(key, path, timestamp, secret)){
            setResponse(response, MiddleResultEnum.PARAM_ERROR.getCode(), MiddleResultEnum.PARAM_ERROR.getValue());
            return Boolean.FALSE;
        }
        // 验证时间戳
        Calendar c = Calendar.getInstance();
        long nowTimestamp = c.getTimeInMillis();
        long reqTimestamp = Long.valueOf(timestamp);
        if ( nowTimestamp - reqTimestamp > TIME){
            setResponse(response, MiddleResultEnum.UNAUTHORIZED.getCode(), MiddleResultEnum.UNAUTHORIZED.getValue());
            return Boolean.FALSE;
        }
        // 验证请求路径
        if (!StringUtils.equals(path, request.getServletPath())) {
            setResponse(response, MiddleResultEnum.BAD_GATEWAY.getCode(), MiddleResultEnum.BAD_GATEWAY.getValue());
            return Boolean.FALSE;
        }
        // 验证秘钥
        if (!StringUtils.equals(key, appKey) || !StringUtils.equals(secret, appSecret)) {
            setResponse(response, MiddleResultEnum.PAYMENT_REQUIRED.getCode(), MiddleResultEnum.PAYMENT_REQUIRED.getValue());
            return Boolean.FALSE;
        }
        return Boolean.TRUE;
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {

    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {

    }
    /**
     * response 返回参数
     */
    private void setResponse(HttpServletResponse response, String code, String msg){
        PrintWriter out = null ;
        try{
            response.setContentType("application/json; charset=utf-8");
            JSONObject res = new JSONObject();
            res.put("code",code);
            res.put("msg",msg);
            out = response.getWriter();
            out.write(res.toString());
            out.flush();
            log.info("OuterControllerHandler setResponse is error result {}", JSON.toJSONString(res) );
        }catch (Exception e){
            log.error("OuterControllerHandler setResponse is Exception {}",e);
        }finally {
            out.close();
        }
    }
}